//
// Created by WangPeng on 2024/8/15.
//

#include "udp_sk.h"
#include <arpa/inet.h>
#include <iostream>
#include <unistd.h>

CUdpSocket::CUdpSocket(std::string serv_ip, int serv_port)
    : serv_ip_(std::move(serv_ip)), serv_port_(serv_port)
{
    udp_fd_ = socket(AF_INET, SOCK_DGRAM, 0);
    if (udp_fd_ < 0)
    {
        return;
    }
    int on = 1;
    setsockopt(udp_fd_, SOL_SOCKET, SO_REUSEADDR, (const char*)&on, sizeof(on));

    //bind ip and port
    struct sockaddr_in addr{};

    addr.sin_family = AF_INET;
    addr.sin_port = htons(serv_port_);

    // 将传入的IP地址转换为网络字节序并设置
    if (inet_pton(AF_INET, serv_ip_.c_str(), &addr.sin_addr) <= 0)
    {
        std::cerr << "Invalid IP address: " << serv_ip_ << std::endl;
        close(udp_fd_);
        exit(EXIT_FAILURE);
    }

    if (bind(udp_fd_, (struct sockaddr*)&addr, sizeof(struct sockaddr)) < 0)
    {
        std::cerr << "bind IP address: " << serv_ip_ << std::endl;
        close(udp_fd_);
        exit(EXIT_FAILURE);
    }
}

void CUdpSocket::init_client_addr(std::string client_ip, int client_port)
{
    client_ip_ = std::move(client_ip);
    client_port_ = client_port;
    addr_.sin_family = AF_INET;
    addr_.sin_port = htons(client_port_);
    // 将传入的IP地址转换为网络字节序并设置
    if (inet_pton(AF_INET, serv_ip_.c_str(), &addr_.sin_addr) <= 0)
    {
        std::cerr << "Invalid IP address: " << serv_ip_ << std::endl;
        close(udp_fd_);
    }
}

ssize_t CUdpSocket::send_udp_package(void *packet, std::size_t len)
{
    return ::sendto(udp_fd_, packet, len, 0, (struct sockaddr*)&addr_, sizeof(addr_));
}

CUdpSocket::CUdpSocket() = default;

CUdpSocket::~CUdpSocket() = default;


